package com.project.config;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.project.dto.ApplyInfoDto;
import com.project.dto.ProcureApplyDto;
import com.project.dto.SupplyRefundRecordDto;
import com.project.dto.UserDto;
import com.project.entity.*;
import com.project.mapper.*;
import com.project.util.ConvertBeanUtil;
import com.rabbitmq.client.Channel;
import org.springframework.amqp.rabbit.annotation.RabbitListener;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.amqp.support.AmqpHeaders;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.messaging.handler.annotation.Header;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import java.io.IOException;
import java.util.List;

/**
 * 监听类
 */
@Service
@Transactional
public class CscRabbitListener {

    @Autowired
    IBiddMapper biddMapper;//折扣率


    @Autowired
    CSCWebSocket cscWebSocket;
    @Autowired
    RabbitTemplate rabbitTemplate;

    @Autowired
    IUserMapper userMapper;  //用户表
    @Autowired
    IUserRecordMapper userRecordMapper; //用户审核记录

    @Autowired
    IUserOrderMapper userOrderMapper;  //用户订单
    @Autowired
    IUserOrderInfoProductMapper userOrderInfoProductMapper; //用户订单商品明细

    @Autowired
    IUserOrderRefundMapper userOrderRefundMapper;  //用户订单退款
    @Autowired
    IUserOrderRefundInfoProductMapper userOrderRefundInfoProductMapper; //用户退款订单商品明细
    @Autowired
    IUserOrderRefundRecordMapper userOrderRefundRecordMapper; //用户退款订单审核记录

    @Autowired
    IProcureApplyMapper procureApplyMapper; //采购申请
    @Autowired
    IApplyInfoMapper applyInfoMapper; //采购申请商品详情

    @Autowired
    IConfirmOrderMapper confirmOrderMapper; //中标确认单的反馈，合同号，改相应的状态

    @Autowired
    ITenderMapper tenderMapper; //供应商投标书

    @Autowired
    ISupplyOrderMapper supplyOrderMapper; //供应商供货单
    @Autowired
    ISupplyGoodsMapper supplyGoodsMapper; //供应商供货单的商品

    @Autowired
    ISupplyRefundMapper supplyRefundMapper; //供应商退货单

    @Autowired
    ISupplierMapper supplierMapper; //供应商表

    @Autowired
    ISupplierRecordMapper supplierRecordMapper; //供应商审核记录

    @Autowired
    IPromotionMapper promotionMapper; //供应商审核记录
    @Autowired
    IChargeRecordMapper chargeRecordMapper; //用户充值记录
    @Autowired
    IPercentMapper percentMapper;//折扣率

    /**
     * 接受客户注册审核申请
     */
    @RabbitListener(queues = "authentication")
    public void authentication(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
//        把JSon转换为对象

        if (StringUtils.hasLength(json)) {
            UserDto userDto = JSONObject.parseObject(json, UserDto.class);

            QueryWrapper<UserEntity> qw = new QueryWrapper<>();
            qw.eq("u_num", userDto.getUserNum());
            UserEntity userEntity = userMapper.selectOne(qw);
            if (userEntity == null) {//该用户第一次审核
                userEntity = new UserEntity();
                userEntity.setUserRef(userDto.getUserNum());
                userEntity.setName(userDto.getUserName());
                userEntity.setPwd(userDto.getPassword());
                userMapper.insert(userEntity);
            } else {
                userEntity.setVerifyStatus(0);
                userMapper.updateById(userEntity);
            }
            ;

            UserRecordEntity userRecordEntity = new UserRecordEntity();
            //验证用户是否重复
            QueryWrapper<UserRecordEntity> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("u_num", userDto.getUserNum());
            queryWrapper.eq("u_status", 0);

            if (!userRecordMapper.exists(queryWrapper)) {

                userRecordEntity.setUserRef(userDto.getUserNum());

                userRecordEntity.setRealName(userDto.getRealName());

                userRecordEntity.setPhone(userDto.getPhone());
                userRecordEntity.setSex(userDto.getSex());
                userRecordEntity.setIdentity(userDto.getIDImg());
                userRecordEntity.setImage(userDto.getQuaImg());
                userRecordEntity.setCompany(userDto.getCompany());
                userRecordEntity.setVerifyTime(null);

                userRecordMapper.insert(userRecordEntity);

                cscWebSocket.SendMessage(CSCWebSocket.USER_PATH);//通知页面来消息了
                //通知业务处理完
            } else {
                System.err.println("用户已存在待审核");
            }
            channel.basicAck(tag, false); //tag标志，false-不批量确认
        }

    }

    /**
     * 接受供应商注册审核
     */
    @RabbitListener(queues = "supplierRegisterQueueOne")
    public void supplierRegisterQueueOne(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
//        把JSon转换为对象
        if (StringUtils.hasLength(json)) {
            SupplierEntity supplierEntity = com.alibaba.fastjson2.JSONObject.parseObject(json, SupplierEntity.class);

            QueryWrapper<SupplierEntity> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("s_supplierRef", supplierEntity.getId());
            if (supplierMapper.exists(queryWrapper)) {//如果订单已存在，则返回
                //通知业务处理完
                System.err.println("用户已存在待审核");
                channel.basicAck(tag, false); //tag标志，false-不批量确认
                return;
            }


            SupplierRecordEntity supplierRecordEntity = com.alibaba.fastjson2.JSONObject.parseObject(json, SupplierRecordEntity.class);
            supplierRecordEntity.setSupplierRef(supplierEntity.getId());
            supplierRecordEntity.setType(supplierEntity.getScope());
            supplierRecordEntity.setIdenty(supplierEntity.getIdentity());
            supplierRecordEntity.setVerifyTime(null);
            supplierRecordEntity.setPrincipalName(supplierEntity.getPrincipalName());
            supplierMapper.insert(supplierEntity);
            supplierRecordMapper.insert(supplierRecordEntity);

            cscWebSocket.SendMessage(CSCWebSocket.SUPPLIER_PATH);//通知页面来消息了
            //通知业务处理完
            channel.basicAck(tag, false); //tag标志，false-不批量确认
        }

    }


    /**
     * 接受用户订单
     */
    @RabbitListener(queues = "addOrder")
    public void addOrder(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
        System.err.println(json);
        //通知业务处理完成
        if (StringUtils.hasLength(json)) {
            UserOrderEntity userOrderEntity = JSONObject.parseObject(json, UserOrderEntity.class);
            QueryWrapper<UserOrderEntity> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("o_orderRef", userOrderEntity.getOrderRef());
            if (userOrderMapper.exists(queryWrapper)) {//如果订单已存在，则返回
                //通知业务处理完
                System.err.println("已存在待审核");
                channel.basicAck(tag, false); //tag标志，false-不批量确认
                return;
            }

            List<UserOrderInfoProductEntity> userOrderInfoProductEntityList = userOrderEntity.getUserOrderInfoProductEntityList();

            userOrderMapper.insert(userOrderEntity);
            QueryWrapper<UserEntity> query = new QueryWrapper<>();
            query.eq("u_num", userOrderEntity.getUserRef());
            double discount = userMapper.selectOne(query).getDiscount();
            for (UserOrderInfoProductEntity u : userOrderInfoProductEntityList) {
                u.setOrderRef(userOrderEntity.getOrderRef());
                u.setTotalPrice(u.getProductPrice() * u.getProductNumber() * discount);
                userOrderInfoProductMapper.insert(u);
            }

            //TODO   提示
            cscWebSocket.SendMessage(CSCWebSocket.USER_PATH);//通知页面来消息了

            //通知业务处理完
            channel.basicAck(tag, false); //tag标志，false-不批量确认
        }
    }


    /**
     * 接受用户退款订单
     */
    @RabbitListener(queues = "returnOrder")
    public void returnOrder(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
        //通知业务处理完成
        System.err.println(json);
        System.err.println("------------------------------------------------------  ");
        //2.添加订单退款表  和 审核记录

        if (StringUtils.hasLength(json)) {

            UserOrderRefundEntity userOrderRefundEntity = JSONObject.parseObject(json, UserOrderRefundEntity.class);
            QueryWrapper<UserOrderRefundEntity> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("r_refundRef", userOrderRefundEntity.getRefundRef());
            if (userOrderRefundMapper.exists(queryWrapper)) {//如果订单已存在，则返回
                System.err.println("数据库已存在");
                //通知业务处理完
                channel.basicAck(tag, false); //tag标志，false-不批量确认
                return;
            }


            QueryWrapper<UserOrderEntity> qw = new QueryWrapper<>();
            qw.eq("o_orderRef", userOrderRefundEntity.getOrderRef());
            UserOrderEntity userOrderEntity = userOrderMapper.selectOne(qw);
            userOrderRefundEntity.setTotalPrice(userOrderEntity.getTotalPrice());


            UserOrderRefundRecordEntity userOrderRefundRecordEntity = ConvertBeanUtil.copy(userOrderRefundEntity, UserOrderRefundRecordEntity.class);
            userOrderRefundRecordEntity.setDate(userOrderRefundEntity.getDateTime());
            userOrderRefundRecordEntity.setTotalPrice(userOrderEntity.getTotalPrice());
            userOrderRefundRecordEntity.setVerifyTime(null);


            userOrderRefundMapper.insert(userOrderRefundEntity);
            userOrderRefundRecordMapper.insert(userOrderRefundRecordEntity);

            cscWebSocket.SendMessage(CSCWebSocket.USER_ORDER_REFUND_PATH);//通知页面来消息了
            //通知业务处理完
            channel.basicAck(tag, false); //tag标志，false-不批量确认
        }

    }


    /**
     * 接受采购申请
     */
    @RabbitListener(queues = "BackPurchaseApplyOne")
    public void BackPurchaseApplyOne(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
        //通知业务处理完成

        if (StringUtils.hasLength(json)) {
            ProcureApplyDto procureApplyDto = JSONObject.parseObject(json, ProcureApplyDto.class);

            QueryWrapper<ProcureApplyEntity> dtoQueryWrapper = new QueryWrapper<>();
            dtoQueryWrapper.eq("a_applyRef", procureApplyDto.getApplyRef());
            if (procureApplyMapper.exists(dtoQueryWrapper)) {//如果订单已存在，则返回
                System.err.println("数据库已存在");
                //通知业务处理完
                channel.basicAck(tag, false); //tag标志，false-不批量确认
                return;
            }


            List<ApplyInfoDto> applyInfoDtoList = procureApplyDto.getApplyInfoEntityList();
            ProcureApplyEntity procureApplyEntity = ConvertBeanUtil.copy(procureApplyDto, ProcureApplyEntity.class);
            List<ApplyInfoEntity> applyInfoEntityList = ConvertBeanUtil.copyList(applyInfoDtoList, ApplyInfoEntity.class);
            procureApplyMapper.insert(procureApplyEntity);
            for (ApplyInfoEntity applyInfoEntity : applyInfoEntityList) {
                applyInfoEntity.setApplyRef(procureApplyEntity.getApplyRef());
                applyInfoMapper.insert(applyInfoEntity);
            }
            cscWebSocket.SendMessage(CSCWebSocket.PROCURE_APPLY_PATH);//通知页面来消息了
            //通知业务处理完
            channel.basicAck(tag, false); //tag标志，false-不批量确认
        }

    }


    /**
     * 接收供应商的中标确认，修改中标确认表为已确认
     */
    @RabbitListener(queues = "sendOrderQueueOne")
    public void sendOrderQueueOne(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
        QueryWrapper<ConfirmOrderEntity> qw = new QueryWrapper<>();
        qw.eq("b_bacp", json);
        ConfirmOrderEntity confirmOrderEntity = confirmOrderMapper.selectOne(qw);
        confirmOrderEntity.setConfirm(1);//已确认
        confirmOrderMapper.updateById(confirmOrderEntity);

        //TODO   把bidd改为已完成
        QueryWrapper<BiddEntity> queryWrapper = new QueryWrapper<>();
        qw.eq("b_biddRef", confirmOrderEntity.getBiddId());
        BiddEntity biddEntity = biddMapper.selectOne(queryWrapper);
        biddEntity.setStatus(2);
        biddMapper.updateById(biddEntity);

        cscWebSocket.SendMessage(CSCWebSocket.USER_PATH);//通知页面来消息了
        //通知业务处理完成
        channel.basicAck(tag, false); //tag标志，false-不批量确认
    }

    /**
     * 接收供应商投标
     */
    @RabbitListener(queues = "sendBiddTableQueueOne")
    public void sendBiddTableQueueOne(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {

            if (StringUtils.hasLength(json)) {
                TenderEntity tenderEntity = JSONObject.parseObject(json, TenderEntity.class);

                tenderEntity.setVerifyTime(null);
                tenderMapper.insert(tenderEntity);
                //TODO   提示
                cscWebSocket.SendMessage(CSCWebSocket.USER_PATH);//通知页面来消息了
                //通知业务处理完
                channel.basicAck(tag, false); //tag标志，false-不批量确认
            }

    }

    /**
     * 接收供应商供货单
     */
    @RabbitListener(queues = "sendSupplyQueueOne")
    public void sendSupplyQueueOne(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
        SupplyOrderEntity supplyOrderEntity = JSONObject.parseObject(json, SupplyOrderEntity.class);
        supplyOrderMapper.insert(supplyOrderEntity);
        List<SupplyGoodsEntity> supplyGoodsEntityList = supplyOrderEntity.getSupplyGoodsEntityList();
        for (SupplyGoodsEntity s : supplyGoodsEntityList) {
            s.setSupplyRef(supplyOrderEntity.getSupplyRef());
            s.setTotalPrice(s.getSum() * s.getPrice());
            supplyGoodsMapper.insert(s);
        }
        //TODO   提示
        cscWebSocket.SendMessage(CSCWebSocket.USER_PATH);//通知页面来消息了

        rabbitTemplate.convertAndSend("topicExchangeTwo", "rabbit.sendSupplyOrder", json);
        //通知业务处理完成
        channel.basicAck(tag, false); //tag标志，false-不批量确认
    }

    /**
     * 接收客户给供应商退货订单
     */
    @RabbitListener(queues = "BackRejectedApplyTwo")
    public void SupplyRefundRecordDto(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
        System.err.println("json = " + json);

        SupplyRefundRecordDto supplyRefundRecordDto = JSONObject.parseObject(json, SupplyRefundRecordDto.class);
        System.out.println("supplyRefundRecordDto = " + supplyRefundRecordDto);
        System.out.println("接收客户给供应商退货订单 json = " + json);


        QueryWrapper<SupplyRefundEntity> dtoQueryWrapper = new QueryWrapper<>();
        dtoQueryWrapper.eq("r_batch", supplyRefundRecordDto.getBatch());
        if (supplyRefundMapper.exists(dtoQueryWrapper)) {//如果订单已存在，则返回
            System.err.println("数据库已存在");
            //通知业务处理完
            channel.basicAck(tag, false); //tag标志，false-不批量确认
            return;
        }
        SupplyRefundEntity refundEntity = ConvertBeanUtil.copy(supplyRefundRecordDto, SupplyRefundEntity.class);
        QueryWrapper<SupplyOrderEntity> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("s_batch", supplyRefundRecordDto.getBatch());
        SupplyOrderEntity supplyOrderEntity = supplyOrderMapper.selectOne(queryWrapper);
        refundEntity.setSupplyRef(supplyOrderEntity.getSupplyRef());
        supplyRefundMapper.insert(refundEntity);

        //TODO   提示
        cscWebSocket.SendMessage(CSCWebSocket.USER_PATH);//通知页面来消息了

        rabbitTemplate.convertAndSend("topicExchangeTwo", "rabbit.SupplyOrderRefundOrder", json);
        //通知业务处理完成
         channel.basicAck(tag, false); //tag标志，false-不批量确认
    }


    /**
     * 接受促销商品审核
     */
    @RabbitListener(queues = "PromotionReviewThree")
    public void PromotionReviewThree(Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long tag, String json) throws IOException {
        try {
            if (StringUtils.hasLength(json)) {
                PromotionEntity promotionEntity = JSONObject.parseObject(json, PromotionEntity.class);


                promotionMapper.insert(promotionEntity);
                cscWebSocket.SendMessage(CSCWebSocket.PROMOTION_PATH);//通知页面来消息了
                //通知业务处理完
                channel.basicAck(tag, false); //tag标志，false-不批量确认
            }
        } catch (Exception e) {
            System.out.println("程序出错");
            e.printStackTrace();
        }

    }


}
